﻿#include "IM_Gate.h"
#include "IM_MessageDef.h"
#include "IM_Agent.h"
#include "Base_Context.h"
#include "IM_Socket_Server.h"
#include "Base_MessageCore.h"
#include "Base_MessageQueue.h"
#include <string>
#include "IM_Account.h"
#include "IM_Login.h"
#include "Token.h"
#include "IM_FriendMap.h"
#include "jsoncpp/json.h"


IM_Agent * IM_Agent::create_agent(IM_Socket_Server * socket_server, int socket_id,IM_Gate * gate)
{
	IM_Agent * a = new IM_Agent();
	a->m_socket_server = socket_server;
	a->m_socket_id = socket_id;
	a->m_gate = gate;


	return a;
}

void IM_Agent::send_data_by_socket_tcp(char * buf, int size)
{
	m_gate->socket_send(m_socket_id, buf, size);
}

IM_Agent::IM_Agent():m_acount(nullptr)
{
	m_contxt = Base_Context::new_base_context();
	Base_MessageCore::register_context(m_contxt);
	m_contxt->callback = [&](Base_Message * m) {this->_proc(m); };
	m_current_state = SocketConnect;
}

IM_Agent::~IM_Agent()
{

}

static int __get_pkt_type(const char *data)
{
	uint16_t pkt_type;
	memcpy(&pkt_type,data, 2);

	DEBUG("pkt_type : %d\n", pkt_type);

	return pkt_type;
}

/*********************************************/

const uint16_t PktType_Login_request = 0;
const uint16_t PktType_Login_Respond = 1;
const uint16_t PktType_GetFriend_Request = 2;
const uint16_t PktType_GetFriend_Respond = 3;

void IM_Agent::_proc(Base_Message * msg)
{
	using namespace std;
	DEBUG("进入agent 处理函数  \n");
	switch (msg->type)
	{
		case IM_MessageType_Socket:
		{
			int pkt_type = __get_pkt_type((char *)msg->data);
			char *data_t = (char *)msg->data + 2;
			int data_size_t = msg->size - 2;
			
			switch (pkt_type)
			{
				case PktType_Login_request:
					_login_handler(data_t,data_size_t);
					break;
				case PktType_GetFriend_Request:
					_get_friend_list_handler(data_t, data_size_t);
					break;
				default:

					break;
			}
		}
		break;

		default:
			break;
	}
	DEBUG("离开agent 处理函数  \n");
}


/**********************************************/



void IM_Agent::_login_handler(char * data, int size)
{
	DEBUG("处理登陆\n");
	std::string  ac = IM_Login::login_check((char *)data,size);
	if (ac.length() == 0)
	{
		IM_Login::login_response_faile(this, LoginRsultCode_None);
	}
	else
	{
		//获取ac
		m_acount = IM_AccountServer::getInstance()->findAccount(ac);
		assert(m_acount);
		auto state = m_acount->get_account_state();
		if (state == AccountState::on_line)
		{
			IM_Login::login_response_faile(this, LoginRsultCode_Repetition);
			return;
		}
		m_token = Token::get_token(ac.c_str());
		IM_Login::login_response_succes(this, m_token);
		m_acount->set_account_state(AccountState::on_line);
	}
}

void IM_Agent::_get_friend_list_handler(char * data, int size)
{
	IM_Protocol::FriendRespond fr;
	
	Json::FastWriter w;
	Json::Value root;
	Json::Value group;
	group["gname"] = "默认分组";

	for (auto v:m_acount->get_friend_map()->get_map())
	{
		Json::Value gmuber;
		IM_Account * ac = v.second;

		gmuber["name"] =ac->get_name();
		gmuber["sex"] = ac->get_sex();
		gmuber["emil"] = ac->get_emil();
		gmuber["id"] = v.first;

		group["gmunber"].append(gmuber);
	}

	root.append(group);

	std::string  s=w.write(root);

	fr.set_data(s);
	fr.set_rcode(0);

	DEBUG("json:%s\nsize:%d", s.c_str(),s.length());
	char buf[2048];
	memcpy(buf, &PktType_GetFriend_Respond, 2);
	fr.SerializeToArray(buf + 2, fr.ByteSizeLong());
	this->send_data_by_socket_tcp(buf, fr.ByteSizeLong()+2);

	DEBUG("发送好友列表\n");
}

